package com.yx.cloud.map.layer;

import android.content.res.Resources;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Canvas;
import android.graphics.DashPathEffect;
import android.graphics.Matrix;
import android.graphics.Paint;
import android.graphics.Path;
import android.graphics.PointF;

import com.aaa.lib.map.MapUtils;
import com.aaa.lib.map.MapView;
import com.aaa.lib.map.area.RectangleArea;
import com.iot.product.sweeper.bean.Furniture;
import com.yx.cloud.R;
import com.yx.cloud.map.YXMapView;
import com.iot.product.sweeper.bean.AreaInfo;
import com.iot.product.sweeper.bean.MapInfo;
import com.iot.common.utils.LogUtils;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;

public class YXFurnitureLayer extends YXAreaLayer<RectangleArea> {
    private static final String TAG = "YXFurnitureLayer";
    public static boolean isForbiddenAreaEditable = false;

    protected int borderColor;

    protected Paint mPaint;       //画笔

    protected Bitmap deleteIcon;  //左上角删除按钮
    protected Bitmap rotateIcon;  //右上角的旋转按钮
    protected Bitmap scaleIcon;   //右下角的缩放按钮
    private Path mRectBorder;
    private Matrix tempMatrix; //当前矩形 相对view的变换，偏移/缩放/旋转
    private float lastPosX;
    private float lastPosY;
    private float lastRtAngle;
    private float areaWidth;
    private float areaHeight;

    public YXFurnitureLayer(MapView mapView) {
        super(mapView);
        Resources resources = mapView.getResources();
        deleteIcon = BitmapFactory.decodeResource(mapView.getContext().getResources(), R.mipmap.area_delete);
        rotateIcon = BitmapFactory.decodeResource(mapView.getContext().getResources(), R.mipmap.area_rotate);
        scaleIcon = BitmapFactory.decodeResource(mapView.getContext().getResources(), R.mipmap.area_drag);


        tempMatrix = new Matrix();

        area = new RectangleArea();
        mRectBorder = new Path();

        borderColor = resources.getColor(R.color.area_stroke);

        mPaint = new Paint();
        mPaint.setStrokeWidth(5);
        mPaint.setStyle(Paint.Style.STROKE);
        mPaint.setAntiAlias(true);
    }

    public void initAreaLayer() {
        MapInfo map = ((YXMapView) mMapView).getMap().getMap();
        float minSize=map.getScreenSize(0.5f);
        float defaultSize= Math.max(map.width/3f,minSize);

        area.setRect(map.width / 2f, map.height / 2f, defaultSize, defaultSize, 0);
        AreaInfo areaInfo = new AreaInfo();
        areaInfo.setType(YXAreaLayer.TYPE_FORBIDDEN_AREA);
        areaInfo.setId(((YXMapView) mMapView).getUniqueAreaId(YXAreaLayer.TYPE_FORBIDDEN_AREA));
        areaInfo.setStamp(new Date().getTime());
        areaInfo.setName("forbidarea-" + areaInfo.getId());
        this.areaInfo = areaInfo;

        focusId = areaInfo.getId();

        areaWidth = map.getActualSize(area.width);
        areaHeight = map.getActualSize(area.height);
        areaSize = areaWidth * areaHeight;

        ((YXMapView) mMapView).setForbiddenAreaChange(this); //新建图层, 设置为已修改
    }

    public void initAreaLayer(Furniture furniture) {
        MapInfo map = ((YXMapView) mMapView).getMap().getMap();

        float x=furniture.getX();
        float y=furniture.getY();


        List<Double> areaVetexs = areaInfo.getBorder();
        area.lt.x = (float) (double) areaVetexs.get(0);
        area.lt.y = (float) (double) areaVetexs.get(1);
        area.rt.x = (float) (double) areaVetexs.get(2);
        area.rt.y = (float) (double) areaVetexs.get(3);
        area.rb.x = (float) (double) areaVetexs.get(4);
        area.rb.y = (float) (double) areaVetexs.get(5);
        area.lb.x = (float) (double) areaVetexs.get(6);
        area.lb.y = (float) (double) areaVetexs.get(7);
        area.setRect(area.lt, area.rt, area.rb, area.lb);
        setAreaInfo(areaInfo);

        areaWidth = map.getActualSize(area.width);
        areaHeight = map.getActualSize(area.height);
        areaSize = areaWidth * areaHeight;
        LogUtils.i("set layer area : " + area.toString());

    }

    @Override
    public AreaInfo getAreaInfo() {
        ArrayList<Double> points = new ArrayList<>();
        points.add((double) area.lt.x);
        points.add((double) area.lt.y);
        points.add((double) area.rt.x);
        points.add((double) area.rt.y);
        points.add((double) area.rb.x);
        points.add((double) area.rb.y);
        points.add((double) area.lb.x);
        points.add((double) area.lb.y);
        areaInfo.setBorder(points);
        return areaInfo;
    }

    @Override
    public boolean isEditable() {
        return isForbiddenAreaEditable;
    }

    @Override
    protected boolean onTouchDown(float x, float y) {
        lastPosX = x;
        lastPosY = y;

        float scale = ((YXMapView)mMapView).getScale();

        //判断点击位置
        if (MapUtils.isPointInCircle(x, y, area.lt, deleteIcon.getWidth() / scale)) {
            operate = OP_DELETE;
            return true;
        } else if (MapUtils.isPointInCircle(x, y, area.rt, rotateIcon.getWidth() / scale)) {
            operate = OP_ROTATE;
            //开始旋转时 设置右上角到圆心的初始角度
            lastRtAngle = MapUtils.getRotateByRect(x, y, area.center.x, area.center.y);
            return true;
        } else if (MapUtils.isPointInCircle(x, y, area.rb, scaleIcon.getWidth() / scale)) {
            operate = OP_SCALE;
            return true;
        } else if (MapUtils.isPointInRectangle(area.lt.x, area.lt.y, area.rt.x, area.rt.y, area.rb.x, area.rb.y, area.lb.x, area.lb.y, x, y)) {
            operate = OP_MOVE;
            return true;
        } else {
            //不在点击范围内 下一位
            operate = OP_NONE;
            return false;
        }
    }

    @Override
    protected boolean onTouchMove(float x, float y) {
        LogUtils.i("YXForbiddenAreaLayer  move to x: " + x + " y : " + y);
        if (operate == OP_MOVE) {
            move(x, y);
            return true;
        }else if (operate == OP_ROTATE) {
            rotate(x, y);
            return true;
        } else if (operate == OP_SCALE) {
            scale(x, y);
            return true;
        } else if (operate == OP_DELETE) {
            return true;
        } else {
            return false;
        }
    }

    @Override
    protected boolean onTouchUp(float x, float y) {
        //判断点击位置
        if (operate == OP_DELETE) {
            delete();
            return true;
        } else if (operate == OP_NONE) {
            return false;
        } else {
            ((YXMapView) mMapView).handleAreaMove(this);
            return true;
        }
    }

    /**
     * 删除
     */
    private void delete() {
        mMapView.getLayerManager().removeLayer(this);
        ((YXMapView) mMapView).setForbiddenAreaChange(this);
    }

    /**
     * 缩放
     *
     * @param x 右下角拉伸到
     * @param y
     */
    private void scale(float x, float y) {
        //获取新rb的点到两条边的距离，即为新矩形宽高
        float h = (float) MapUtils.pointToLine(x, y, area.lt.x, area.lt.y, area.rt.x, area.rt.y);
        float w = (float) MapUtils.pointToLine(x, y, area.lt.x, area.lt.y, area.lb.x, area.lb.y);

        MapInfo map = ((YXMapView) mMapView).getMap().getMap();

        float realW = map.getActualSize(w);
        float realH = map.getActualSize(h);
        //矩形实际长宽小于0.5 设置为0.5
        if (realW < MIN_AREA_REAL_WIDTH) {
            w = map.getScreenSize(MIN_AREA_REAL_WIDTH);
        }
        if (realH < MIN_AREA_REAL_WIDTH) {
            h = map.getScreenSize(MIN_AREA_REAL_WIDTH);
        }

        if (realH * realW > MAX_AREA_SIZE) {
            //如果超过大小 就计算触摸点与左上角的连线  再将其缩小到MAX_AREA_SIZE长度  分别对宽高做缩放就能得到当前的w和h
            float scale = (float) Math.sqrt(MAX_AREA_SIZE / (realH * realW));
            w = map.getScreenSize(realW * scale);
            h = map.getScreenSize(realH * scale);
        }


        LogUtils.i("w: " + w + " h " + h + " real w " + realW + " real h: " + realH);
//      图标之间留间隙 不能重叠
//        mMapView.getTransform().getValues(tempMatrixValue);
//        float scale = tempMatrixValue[0];
//        if (h < 2 * deleteIcon.getWidth() / scale) {
//            //矩形太小 不操作
//            h = 2 * deleteIcon.getWidth() / scale;
//        }
//
//        if (w < 2 * deleteIcon.getWidth() / scale) {
//            w = 2 * deleteIcon.getWidth() / scale;
//        }


        //这里如果简单通过右下角来设置中心点 ， 缩放到最小后 会把控件推走。 不删是因为 还蛮好玩的。。。。
        //        center.x = (lt.x + x) / 2;
        //        center.y = (lt.y + y) / 2;

        //计算中心点  现在知道旋转角度 ， 以及高宽，  求出对角钱长度一半 算出当前对角线的的角度  从0度旋转到当前角度  获取到中心点
        float degree = (float) (180 * Math.atan2(h, w) / Math.PI);
        tempMatrix.setRotate(area.rotate + degree, area.lt.x, area.lt.y);
        //中心点X=左上角X+ 半对角线长  中心点Y= 左上角Y+0
        float centerX = area.lt.x + (float) Math.sqrt(w * w + h * h) / 2;
        float centerY = area.lt.y;
        MapUtils.getTransformedPoint(tempMatrix, centerX, centerY, area.center);

        area.setRect(area.center, w, h, area.rotate);

        areaWidth = map.getActualSize(area.width);
        areaHeight = map.getActualSize(area.height);
        areaSize = areaWidth * areaHeight;

        ((YXMapView) mMapView).setForbiddenAreaChange(this);
        mMapView.refresh();
    }


    /**
     * 平移
     *
     * @param x
     * @param y
     */
    private void move(float x, float y) {
        //计算平移距离
        float translateX = x - lastPosX;
        float translateY = y - lastPosY;

        //移动中心点
        area.setCenter(area.center.x + translateX, area.center.y + translateY);

        //记录上次触摸点
        lastPosX = x;
        lastPosY = y;

        ((YXMapView) mMapView).setForbiddenAreaChange(this);

        mMapView.refresh();
    }

    /**
     * 旋转
     *
     * @param x
     * @param y
     */
    private void rotate(float x, float y) {
        //获取旋转后 右上角到圆心的角度
        float rtEndRotation = MapUtils.getRotateByRect(x, y, area.center.x, area.center.y);
        //当前旋转角度等于  之前的角度 加上增量
        float tempRotate = area.rotate + rtEndRotation - lastRtAngle;

        area.setRotate(tempRotate);
        lastRtAngle = rtEndRotation;

        ((YXMapView) mMapView).setForbiddenAreaChange(this);

        mMapView.refresh();
    }

    @Override
    public void draw(Canvas canvas) {
        if (!visible) {
            return;
        }
        //        drawWithMatrix(canvas);
        drawWithMatrixValue(canvas);
    }

    public void drawWithMatrixValue(Canvas canvas) {
        float scale = ((YXMapView)mMapView).getScale();
        canvas.save();
        canvas.setMatrix(mMapView.getTransform());
        drawRect1(canvas, scale);
        canvas.restore();

        if (isEditable() && focusId == areaInfo.getId()) {
            drawIcon1(canvas, scale);
        }
    }


    public PointF getCenter() {
        return area.center;
    }

    /**
     * 绘制删除 旋转 缩放按钮
     *
     * @param canvas
     */
    private void drawIcon(Canvas canvas) {
        canvas.drawBitmap(deleteIcon, area.lt.x - deleteIcon.getWidth() / 2, area.lt.y - deleteIcon.getHeight() / 2, null);

        canvas.drawBitmap(rotateIcon, area.rt.x - rotateIcon.getWidth() / 2, area.rt.y - rotateIcon.getHeight() / 2, null);

        canvas.drawBitmap(scaleIcon, area.rb.x - scaleIcon.getWidth() / 2, area.rb.y - scaleIcon.getHeight() / 2, null);
    }

    public void drawRect1(Canvas canvas, float scale) {
        mPaint.setStrokeWidth(5 / scale);
        //设置边框
        setBorder(area);

        //画边框
        mPaint.setStyle(Paint.Style.STROKE);
        mPaint.setColor(borderColor);
        mPaint.setPathEffect(new DashPathEffect(new float[]{15 / scale, 8 / scale}, 0));
        canvas.drawPath(mRectBorder, mPaint);

    }

    private void setBorder(RectangleArea area) {
        mRectBorder.reset();
        mRectBorder.moveTo(area.lt.x, area.lt.y);
        mRectBorder.lineTo(area.rt.x, area.rt.y);
        mRectBorder.lineTo(area.rb.x, area.rb.y);
        mRectBorder.lineTo(area.lb.x, area.lb.y);
        mRectBorder.close();
    }

    private void drawIcon1(Canvas canvas, float scale) {
        getTransformedPoint(mMapView.getTransform(), area.lt.x - deleteIcon.getWidth() / 2f / scale, area.lt.y - deleteIcon.getHeight() / 2f / scale);
        canvas.drawBitmap(deleteIcon, tmpPoint[0], tmpPoint[1], null);

        getTransformedPoint(mMapView.getTransform(), area.rt.x - rotateIcon.getWidth() / 2f / scale, area.rt.y - rotateIcon.getHeight() / 2f / scale);
        canvas.drawBitmap(rotateIcon, tmpPoint[0], tmpPoint[1], null);

        getTransformedPoint(mMapView.getTransform(), area.rb.x - scaleIcon.getWidth() / 2f / scale, area.rb.y - scaleIcon.getHeight() / 2f / scale);
        canvas.drawBitmap(scaleIcon, tmpPoint[0], tmpPoint[1], null);
    }



}
